package lambdademo;
/*
1. 如果一个接口只有一个抽象方法，那么该接口就是一个函数式接口
2. 如果我们在某个接口上声明了 @FunctionalInterface 注解，那么编译器就会按照函数式接口的定义来要求该接
    口，这样如果有两个抽象方法，程序编译就会报错的。所以，从某种意义上来说，只要你保证你的接口中只
    有一个抽象方法，你可以不加这个注解。加上就会自动进行检测的。
 */

import java.util.ArrayList;
import java.util.HashMap;

//无返回值无参数
@FunctionalInterface
interface NoParameterNoReturn {
    void test();
}
//无返回值一个参数
@FunctionalInterface
interface OneParameterNoReturn {
    void test(int a);
}
//无返回值多个参数
@FunctionalInterface
interface MoreParameterNoReturn {
    void test(int a,int b);
}


//有返回值无参数
@FunctionalInterface
interface NoParameterReturn {
    int test();
}
//有返回值一个参数
@FunctionalInterface
interface OneParameterReturn {
    int test(int a);
}
//有返回值多参数
@FunctionalInterface
interface MoreParameterReturn {
    int test(int a,int b);
}


public class Test {

    public static void main(String[] args) {
        HashMap<String,Integer> map = new HashMap<>();
        map.put("hello",2);
        map.put("abc",22);
        map.put("def",89);

        /*map.forEach(new BiConsumer<String, Integer>() {
            @Override
            public void accept(String s, Integer integer) {
                System.out.println("key:" +s+ "  val:" +integer);
            }
        });*/
//        map.forEach((key,val)-> {System.out.println("key:" +key+ "  val:" +val);});
        map.forEach((key,val)-> System.out.println("key:" +key+ "  val:" +val));
    }

    public static void main9(String[] args) {
        ArrayList<String> list = new ArrayList<>();
        list.add("Hello");
        list.add("bit");
        list.add("hello");
        list.add("lambda");
        /*list.forEach(new Consumer<String>(){
            @Override
            public void accept(String str){
                //简单遍历集合中的元素。
                System.out.print(str+" ");
            }
        });*/

        list.forEach(s -> System.out.println(s));

        System.out.println("===============");

        /*list.sort(new Comparator<String>() {
            @Override
            public int compare(String o1, String o2) {
                return o1.compareTo(o2);
            }
        });*/
        list.sort((x,y)->x.compareTo(y));
        list.forEach(s-> System.out.println(s));
    }

    public static void main8(String[] args) {
        int a = 10;
//        a = 100;  不可以改变值
        NoParameterNoReturn noParameterNoReturn = new NoParameterNoReturn() {
            @Override
            public void test() {
                System.out.println("这是test方法");
                System.out.println(a);         // 这里是一个常量，或者是一个没有改变过值的变量
            }
        };
        noParameterNoReturn.test();
    }

    public static void main7(String[] args) {
//        MoreParameterReturn moreParameterReturn = (x,y)->{return x+y;};
        MoreParameterReturn moreParameterReturn = (x,y)-> x+y;
        System.out.println(moreParameterReturn.test(10,20));
    }

    public static void main6(String[] args) {
//        OneParameterReturn oneParameterReturn = (x)->{return x+1;};
        OneParameterReturn oneParameterReturn = (x)-> x+1;
        System.out.println(oneParameterReturn.test(10));
    }

    public static void main5(String[] args) {
//        NoParameterReturn noParameterReturn = ()->{return 10;};
        NoParameterReturn noParameterReturn = ()-> 10; //有一个返回值时可以省略return
        int ret = noParameterReturn.test();
        System.out.println(ret);
    }

    public static void main4(String[] args) {
        MoreParameterNoReturn moreParameterNoReturn = (x,y)-> System.out.println(x+y);
        MoreParameterNoReturn moreParameterNoReturn1 = (int x,int y)-> System.out.println(x+y);
        moreParameterNoReturn.test(10,30);
    }

    public static void main3(String[] args) {
//        OneParameterNoReturn oneParameterNoReturn = (x)->{System.out.println(x);}; //如果只有一个语句可以省略{}
        OneParameterNoReturn oneParameterNoReturn = x-> System.out.println(x); //如果参数只有一个可以去掉小括号
//        OneParameterNoReturn oneParameterNoReturn = System.out::println; //方法的引用，不用了解
        oneParameterNoReturn.test(10);

    }

    public static void main2(String[] args) {
        NoParameterNoReturn noParameterNoReturn = ()-> System.out.println("这是test方法");
        noParameterNoReturn.test();
    }

    public static void main1(String[] args) {
        //相当于是匿名内部类
        NoParameterNoReturn noParameterNoReturn = new NoParameterNoReturn(){  //实现了一个接口
            @Override
            public void test() {   //重写了接口里的方法
                System.out.println("这是test方法");
            }
        };
        noParameterNoReturn.test();
    }
}
